package com.sensetime.jv.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.LambdaUpdateWrapper;
import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.conditions.query.LambdaQueryChainWrapper;
import com.baomidou.mybatisplus.extension.conditions.update.LambdaUpdateChainWrapper;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.sensetime.jv.entity.PermissionsJv;
import com.sensetime.jv.entity.RolePermissionsJv;
import com.sensetime.jv.entity.UrlPermissionsJv;
import com.sensetime.jv.mapper.PermissionsMapper;
import com.sensetime.jv.mapper.RolePermissionsMapper;
import com.sensetime.jv.mapper.UrlPermissionsMapper;
import com.sensetime.jv.service.PermissionService;
import com.sensetime.jv.service.UrlPermissionService;
import com.sensetime.jv.service.UserRoleCacheService;
import com.sensetime.jv.util.AssertUtil;
import com.sensetime.jv.vo.request.PermissionListReqVO;
import com.sensetime.jv.vo.request.PermissionSaveReqVO;
import com.sensetime.jv.vo.request.PermissionUrlEditReqVO;
import com.sensetime.jv.vo.response.PermissionRespVO;
import lombok.AllArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.List;
import java.util.Objects;

@Service
@Slf4j
@AllArgsConstructor
public class PermissionServiceImpl implements PermissionService {


    @Autowired
    private PermissionsMapper mapper;
    @Autowired
    private UrlPermissionsMapper urlPermissionsMapper;
    private final PermissionsMapper permissionsMapper;
    private final RolePermissionsMapper rolePermissionsMapper;
    private final UrlPermissionService urlPermissionService;
    private final UserRoleCacheService userRoleCacheService;

    @Override
    public PageInfo<PermissionRespVO> list(String name, Integer page, Integer size) {
        if (page == null || size == null){
            page = 1;
            size=10;
        }
        PageHelper.startPage(page,size);
        List<PermissionRespVO> permissionRespVOS = mapper.selectByName(name);
        return new PageInfo<>(permissionRespVOS);
    }


    @Override
    public void deleteById(Long id) {
        UrlPermissionsJv urlPermissionsJv = urlPermissionsMapper.selectById(id);
        AssertUtil.notNull(urlPermissionsJv,"接口权限不存在，请检查");
        urlPermissionsJv.setPermissionId(null);
        new LambdaUpdateChainWrapper<>(urlPermissionsMapper).eq(UrlPermissionsJv::getId,id).set(UrlPermissionsJv::getPermissionId,null).update();
        urlPermissionService.removeAll();
    }

    @Override
    public void updateById(PermissionUrlEditReqVO reqVO) {
        AssertUtil.notNull(permissionsMapper.selectById(reqVO.getPermissionId()),"权限不存在");
        AssertUtil.notNull(urlPermissionsMapper.selectById(reqVO.getId()),"接口权限信息不存在");
        List<UrlPermissionsJv> list = new LambdaQueryChainWrapper<>(urlPermissionsMapper).eq(UrlPermissionsJv::getUrl, reqVO.getUrl()).eq(UrlPermissionsJv::getMethod, reqVO.getMethod()).list();
        AssertUtil.isTrue(list.stream().anyMatch(item-> Objects.equals(reqVO.getId(),item.getId())),"接口权限信息重复，请重新修改再提交");
        UrlPermissionsJv urlPermissionsJv = new UrlPermissionsJv();
        BeanUtils.copyProperties(reqVO,urlPermissionsJv);
        urlPermissionsMapper.updateById(urlPermissionsJv);
        urlPermissionService.removeAll();

    }



    /* ---------- permissions 表 ---------- */
    @Override
    public PageInfo<PermissionsJv> listPermissions(PermissionListReqVO vo) {
        PageHelper.startPage(vo.getPage(), vo.getSize());
        List<PermissionsJv> permissionsJvs = permissionsMapper.selectList(
                Wrappers.<PermissionsJv>lambdaQuery()
                        .like(vo.getPermissionName() != null,
                                PermissionsJv::getPermissionName, vo.getPermissionName()));
        return new PageInfo<>(permissionsJvs);
    }

    @Override
    public PermissionsJv getPermissionById(Integer id) {
        return permissionsMapper.selectById(id);
    }

    @Override
    @Transactional
    public Integer savePermission(PermissionSaveReqVO vo) {
        PermissionsJv p = new PermissionsJv();
        p.setId(vo.getId());
        p.setPermissionName(vo.getPermissionName());
        boolean exists = new LambdaQueryChainWrapper<>(permissionsMapper)
                .eq(PermissionsJv::getPermissionName, p.getPermissionName())
                .notIn(Objects.nonNull(p.getId()),PermissionsJv::getId,p.getId()).exists();
        AssertUtil.isTrue(!exists,"权限名重复，请检查再提交");
        if (vo.getId() == null) {
            permissionsMapper.insert(p);
        } else {
            PermissionsJv permissionsJv = permissionsMapper.selectById(p.getId());
            AssertUtil.notNull(permissionsJv,"当前权限不存在");
            permissionsMapper.updateById(p);
            updateUserInfo(vo.getId());

        }
        urlPermissionService.removeAll();
        return p.getId();
    }

    private void updateUserInfo(Integer permissionId) {
        // 使用LambdaQueryWrapper构造查询条件
        LambdaQueryWrapper<RolePermissionsJv> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(RolePermissionsJv::getPermissionId, permissionId);

        // 调用Mapper的selectList方法查询
        List<RolePermissionsJv> result = rolePermissionsMapper.selectList(queryWrapper);
        if (CollectionUtils.isEmpty(result))return;
        for (RolePermissionsJv rolePermissionsJv : result) {
            userRoleCacheService.updateUserRole(rolePermissionsJv.getRoleId());
        }
    }


    private void updateUserInfo(List<RolePermissionsJv> result) {
        if (CollectionUtils.isEmpty(result))return;
        for (RolePermissionsJv rolePermissionsJv : result) {
            userRoleCacheService.updateUserRole(rolePermissionsJv.getRoleId());
        }
    }

    @Override
    @Transactional
    public void deletePermission(Integer id) {
        PermissionsJv permissionsJv = permissionsMapper.selectById(id);
        AssertUtil.notNull(permissionsJv,"当前权限不存在");
        List<RolePermissionsJv> list = new LambdaQueryChainWrapper<>(rolePermissionsMapper).eq(RolePermissionsJv::getPermissionId, id).list();
        // 解绑角色
        rolePermissionsMapper.delete(Wrappers.<RolePermissionsJv>lambdaQuery()
                .eq(RolePermissionsJv::getPermissionId, id));
//        // 解绑 URL
        LambdaUpdateWrapper<UrlPermissionsJv> lambdaQueryWrapper = new LambdaUpdateWrapper<UrlPermissionsJv>().eq(UrlPermissionsJv::getPermissionId, permissionsJv.getId()).set(UrlPermissionsJv::getPermissionId, null);
        urlPermissionsMapper.update(lambdaQueryWrapper);

        permissionsMapper.deleteById(id);
        updateUserInfo(list);
        urlPermissionService.removeAll();

    }



}
